/*
 * File:   Griewank.h
 * Author: jcrada
 *
 * Created on 12 November 2010, 8:47 AM
 */

#ifndef ECB_GRIEWANK_H
#define	ECB_GRIEWANK_H

#include "ecb/base/Problem.h"
#include <cmath>

namespace ecb {

    /* Source:
     * @incollection{springer-dif.evo,
           Author = {Price, Kenneth and Storn, Rainer M. and Lampinen, Jouni A.},
           title={{Appendix}},
           booktitle = {Differential Evolution: A Practical Approach to Global Optimization},
           series={Natural Computing Series},
           editor={Rozenberg, G. and Bäck, Th. and Eiben, A. E. and Kok, J. N. and Spaink, H. P.},
           publisher = {Springer-Verlag Berlin Heidelberg},
           pages = {513-533},
           year = {2005}
           }
     */
    class Griewank : public Problem {
    public:

        Griewank(const std::string& id = "Griewank", const std::string& name = "Griewank",
                int dimensions = 0, scalar minimum = -600, scalar maximum = 600,
                bool minimization = true) :
        Problem(id, name, dimensions, minimum, maximum, minimization) { }

        scalar f(const std::vector<scalar>& x) {
            scalar sum = 0.0, prod = 1.0;
            for (size_t i = 0; i < x.size(); ++i) {
                sum += x[i] * x[i];
                prod *= std::cos(x[i] / std::sqrt(i + 1.0));
            }
            return 1.0 + (1.0 / 4000.0) * sum - prod;
        }
    };

}

#endif	/* ECB_GRIEWANK_H */

